improvement(workflow): polish canvas interactions and execution states - #5976
improvement(workflow): polish canvas interactions and execution states#5976andresdjasso wants to merge 7 commits into
Conversation
PR SummaryMedium Risk Overview Cards and actions: Block canvas content: Titles and type tags come from New connected-block flow: Realtime / execution: Edge inserts canonicalize source/target handles via Reviewed by Cursor Bugbot for commit 7f6cc9c. Bugbot is set up for automated code reviews on this repo. Configure here. |
Greptile SummaryCanonicalizes workflow edge handles throughout realtime persistence.
Confidence Score: 5/5The PR appears safe to merge. No blocking failure remains; the previously reported realtime canonicalization gap is addressed across the applicable persistence paths.
|
| Filename | Overview |
|---|---|
| apps/realtime/src/database/operations.ts | All relevant realtime edge persistence paths now canonicalize positioned handles, and duplicate checks normalize both candidate and existing edges. |
| packages/workflow-types/src/workflow.ts | Shared source and target canonicalizers collapse legacy positional aliases while retaining distinct semantic routing handles. |
Reviews (2): Last reviewed commit: "fix(workflow): canonicalize realtime edg..." | Re-trigger Greptile
Connection anchors: an output now always leaves a card from the right.
The cursor swell lets a drag start on any edge, but the left side is the
input, so anchoring an outgoing edge there drew a line out of the input
port and read as a second input. `normalizeCursorSourceHandleId` resolves
every drag to the right anchor, `normalizePositionedSourceHandleId`
collapses `source-left` alongside the legacy vertical anchors (so data
from the API, an older client, or a stale save self-heals on load), and
only the right-side source anchor is mounted.
Drops in `onConnectEnd` are always source -> target. The branch that
reversed the edge for a drag starting on an input could never run: the
`target` handle is `isConnectableStart={false}` and the positioned side
anchors are `isConnectable={false}`, so React Flow never reports an input
as a drag origin. Removed it and its now-unused imports.
A newly created block is centered once its node mounts and is measured,
so a card added from a drag-release, the block menu, or the toolbar is
never left off-screen or under the editor panel.
The editor panel's block icon uses the same type accent as the card's
badge instead of the block's legacy `bgColor`, which had left the panel
on the old per-integration brand colours.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
The Start card intermittently collapsed after load, squashing the action-menu tab so its icon row sat over the card. `.workflow-drag-handle` is the host the border renderer measures, and both it and the header row took their height from `blockHeight && blockHeight > 0`. `blockHeight` comes from the deterministic-dimensions pass and is already floored at MIN_PAINTED_HEIGHT (48), but it is absent on the first frames — and with no floor the host collapsed to its natural content height (25.5px for a header-only trigger, exactly the title's line box). The border builds its perimeter from `host.offsetHeight`, so that window painted a sub-floor card: too little straight edge remained on the vertical runs for the action-menu tab, which collapsed into the corner arcs. Whether you saw it depended purely on whether the dimension publish had landed, which is why it reproduced on one workflow and not another. Floor all three: the host, the header row (so `items-center` centres the title and type tag rather than pinning them to the top), and the border's own `offsetHeight` read. Also raise ACTION_MENU_CONTENT_READY_THRESHOLD to 0.9. At 0.8 the 24px icon row was revealed while the swell had only reached 22.4px of its 28px — shorter than the row it contains. Secondary to the above, but a real overflow window on its own. The test now pins the ratio rather than the constant. Tag palette moves to fixed brand values (hex, not derived oklch) with two inks — #F8F8F8 on dark fills, #1A1A1A on light. Tones are renamed to match what they render. `green` (2.55:1) and `orange` (3.15:1) sit under WCAG AA against their paired ink; both are deliberate brand decisions and are documented in the component. Deploy and Run take two new Button variants rather than className overrides, so `tertiary` stays green everywhere else. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
ace5467 to
abf8385
Compare
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
@cursor review |
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes using high effort and found 1 potential issue.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.
Reviewed by Cursor Bugbot for commit 7f6cc9c. Configure here.
|
|
||
| logger.debug(`Updated block error output: ${payload.id} -> ${payload.errorEnabled}`) | ||
| break | ||
| } |
There was a problem hiding this comment.
Error toggle lost on replace
Medium Severity
UPDATE_ERROR_ENABLED persists errorEnabled into block data, but the client store only updates the top-level field and REPLACE_STATE rewrites blocks from block.data alone without merging that top-level value the way full saves do. After undo/redo or any replace-state, a later reload can drop an enabled error output that has no error edge yet.
Additional Locations (1)
Reviewed by Cursor Bugbot for commit 7f6cc9c. Configure here.


Summary
What changed
Cards and execution
Information hierarchy and tags
Send Email,Wait for Input) while preserving provider/type tags and internal unique block names.Loop containers
Connected block selector and notes
Type of Change
Testing
@sim/workflow-rendererandsimtype checks passed after syncing dependencies to the rebased lockfile.Checklist
staging.